// ControlSocket.h : header file

#if !defined(AFX_CONTROLSOCKET_H__B7C54BD3_A555_11D0_8996_00AA00B92B2E__INCLUDED_)
#define AFX_CONTROLSOCKET_H__B7C54BD3_A555_11D0_8996_00AA00B92B2E__INCLUDED_

#if _MSC_VER >= 1000
#pragma once
#endif // _MSC_VER >= 1000

#include "UserManager.h"

class CDataSocket;
class CClientThread;

#define FTP_DOWNLOAD	1
#define FTP_UPLOAD		2
#define FTP_RENAME		3
#define FTP_DELETE		4
#define FTP_CREATE_DIR	5
#define FTP_LIST		6

enum
{
	STATUS_IDLE		= 0,
	STATUS_LOGIN	= 1,
	STATUS_LIST		= 2,
	STATUS_UPLOAD	= 3,
	STATUS_DOWNLOAD	= 4,
};


class CControlSocket : public CSocket
{
	enum // Token ID's
	{
		TOK_ABOR, TOK_APPE, TOK_BYE, TOK_CDUP, 
		TOK_CWD, TOK_DELE, TOK_HELP, TOK_LIST, 
		TOK_MKD, TOK_NLST, TOK_NOOP, TOK_PASS, 
		TOK_PASV, TOK_PASW, TOK_PORT, TOK_PWD, 
		TOK_QUIT, TOK_REST, TOK_RETR, TOK_RMD, 
		TOK_RNFR, TOK_RNTO, TOK_SIZE, TOK_STOR, 
		TOK_SYST, TOK_TYPE, TOK_USER, TOK_XCWD, 
		TOK_XMKD, TOK_XPWD, TOK_XRMD, TOK_ERROR,
	};

public:
	struct CFTPCommand
	{
		int m_nTokenID;
		char *m_pszName;
		BOOL m_bHasArguments;
		char *m_pszDescription;
	};

// Attributes
public:
	BOOL SendResponse(LPCTSTR pstrFormat, ...);
	void PostStatusMessage(LPCTSTR lpszStatus, int nType);
	BOOL GetCommand(CString &command, CString &args);
	BOOL CreateDataConnection();
	void DestroyDataConnection();
// Operations
public:
	CControlSocket();
	virtual ~CControlSocket();

	void ProcessCommand();
	void GetCommandLine();

// Overrides
public:
	CWinThread* m_pThread;

	CString m_strUserName;
	// ClassWizard generated virtual function overrides
	//{{AFX_VIRTUAL(CControlSocket)
	public:
	virtual void OnClose(int nErrorCode);
	virtual void OnReceive(int nErrorCode);
	//}}AFX_VIRTUAL

	// Generated message map functions
	//{{AFX_MSG(CControlSocket)
		// NOTE - the ClassWizard will add and remove member functions here.
	//}}AFX_MSG

// Implementation
protected:
	int m_bPassiveMode;
	
	int m_nRemotePort;
	CString m_strRemoteHost;
	
	CDataSocket *m_pDataSocket;

	int m_nStatus;
	
	CStringList m_strCommands;
	
	CString m_RxBuffer;
	CString m_strCurrentDir;

	friend CClientThread;
	friend CDataSocket;

	CUser m_User;

	BOOL GetDirectoryList(LPCTSTR lpszDirectory, CString &strResult);
	BOOL GetLocalPath(LPCTSTR lpszRelativePath, CString &strLocalPath);
	BOOL GetRelativePath(LPCTSTR lpszLocalPath, CString &strRelativePath);
	int CheckDirectory(CString dirname, int nOption, CString &strResult);
	int CheckFileName(CString filename, int nOption, CString &strResult);
	BOOL CheckAccessRights(LPCTSTR lpszDirectory, int nOption);

	void DoChangeDirectory(LPCTSTR lpszDirectory);
};

/////////////////////////////////////////////////////////////////////////////

//{{AFX_INSERT_LOCATION}}
// Microsoft Developer Studio will insert additional declarations immediately before the previous line.

#endif // !defined(AFX_CONTROLSOCKET_H__B7C54BD3_A555_11D0_8996_00AA00B92B2E__INCLUDED_)
